package com.demo.web;

import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cglib.proxy.Enhancer;
import org.springframework.cglib.proxy.MethodInterceptor;
import org.springframework.cglib.proxy.MethodProxy;

import java.lang.reflect.Method;

@SpringBootApplication
@Slf4j
public class MetaSpaceOOM {

    static class OOM{}

    /**
     * 模拟Metaspace空间溢出，我们不断生成类往元空间灌，类占据的空间是会超过Metaspace指定的空间大小的
     * @param args
     */
    public static void main(String[] args) {
        // 运行本程序之前请先设置VM Options
        // -XX:MetaspaceSize=10m -XX:MaxMetaspaceSize=10m  -XX:+PrintGCDetails
        // java.lang.OutOfMemoryError: Metaspace
        int i = 0;//模拟计数多少次以后发生异常
        try {
            while (true){
                log.info(String.valueOf(i));
                i++;
                Enhancer enhancer = new Enhancer();
                enhancer.setSuperclass(MetaSpaceOOM.OOM.class);
                enhancer.setUseCache(false);
                enhancer.setCallback(new MethodInterceptor() {
                    @Override
                    public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
                        return methodProxy.invokeSuper(o,args);
                    }
                });
                enhancer.create();
            }
        } catch (Throwable e) {
            System.out.println("=================多少次后发生异常："+i);
            e.printStackTrace();
        }
    }

}
